package susebs.pb.travel_server.controller;

import com.github.pagehelper.PageInfo;
import org.springframework.web.bind.annotation.*;
import susebs.pb.travel_server.domain.DetailUser;
import susebs.pb.travel_server.domain.Locations;
import susebs.pb.travel_server.domain.PageDto;
import susebs.pb.travel_server.domain.Result;
import susebs.pb.travel_server.entity.Hotels;
import susebs.pb.travel_server.entity.Landmarks;
import susebs.pb.travel_server.entity.Pictures;
import susebs.pb.travel_server.entity.Users;
import susebs.pb.travel_server.service.*;
import susebs.pb.travel_server.utils.MapInfoBasicUtil;
import susebs.pb.travel_server.utils.NavigationUtil;
import susebs.pb.travel_server.utils.TimeFormatUtil;

import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;

/**
 * 用户表控制层
 */
@RestController
@RequestMapping("/users")
@CrossOrigin
public class UsersController {

    @Resource
    private UsersService usersService;
    @Resource
    private PicturesService picturesService;
    @Resource
    private LandmarksService landmarksService;
    @Resource
    private HotelsService hotelsService;
    @Resource
    private NavigationsService navigationsService;

    private DetailUser oldUser;

    /**
     * 通过用户id查询信息
     * 请求时机：
     * 1.刚进入用户界面
     * 2.每次修改成功时请求重新刷新数据（头像/定位/角色/普通信息）
     */
    @GetMapping("/queryUserById")
    public Result<Users> queryUserById(Long userId){
        Users user = usersService.queryById(userId);
        String city = "";
        //获取用户城市信息
        if(user.getUserAddr()!=null){
            String[] parts = user.getUserAddr().split("省|市|区");
            city = parts[1] + "市";
        }
        Result<Users> res = Result.buildSuccess(user);
        res.add("city",city);
        res.add("registerTime", TimeFormatUtil.timeFormat(user.getRegisterTime()));
        res.add("latestLoginTime", TimeFormatUtil.timeFormat(user.getLatestLoginTime()));
        return res ;
    }


    /**
     * 准备进入修改界面，存储用户信息
     * 请求时机：点击“修改个人信息”时发起请求
     */
    @GetMapping("/storageOldUser")
    public Result storageOldUser(Long userId){
        oldUser = new DetailUser();

        Users user = usersService.queryById(userId);
        Pictures pic = picturesService.getUserOldPic(user.getUserId());

        oldUser.setUsers(user);
        oldUser.setPictures(pic);

        System.out.println(oldUser);

        return Result.buildSuccess();
    }


    /**
     * 修改头像
     * 先根据userId将原pic关联的entityId设为空
     * 随后将新的pic关联id设置为userId
     * @param picId 用户新关联的图片id
     * @param userId 用户id
     * @return 头像修改成功与否的消息
     */
    @GetMapping("/updateUserImg")
    public Result updateUserImg(Long picId,Long userId){
        Pictures newPic = picturesService.queryById(picId);
        Pictures oldPic = picturesService.queryPicturesByOwner(4, userId).get(0);

//        System.out.println("oldPic:"+oldPic);
//        System.out.println("newPic:"+newPic);


        //将原先图片关联的用户id设为空
        oldPic.setPicOwnerEntityId(null);
        Pictures old = picturesService.update(oldPic);
//        System.out.println("old:"+old);
        if(old.getPicOwnerEntityId() != null){
            return Result.buildFail("原始头像删除失败！");
        }

        //设置新的图片关联id
        newPic.setPicOwnerEntityId(userId);
        Pictures news = picturesService.update(newPic);
//        System.out.println("news:"+news);
        if(!Objects.equals(news.getPicOwnerEntityId(), userId)){
            return Result.buildFail("头像修改失败！");
        }

        return Result.buildSuccess();
    }


    /**
     * 修改定位
     * 根据传来的code进行地址解析/编码
     * @param locations 包含标识符，经纬度或详细地址字符串的地址实体
     * @return 定位修改成功与否的消息
     */
    @PostMapping("/updateUserAddr")
    public Result updateUserAddr(@RequestBody Locations locations) throws Exception {
//        System.out.println("updateUserAddr--locations:"+locations);

        //user实体暂存
        Users user = oldUser.getUsers();

        //标识符非空判断
        if(locations.getCode() == null){
            return Result.buildFail("标识符不能为空！请传入标识符！\n code：0，地址解析\n code：1，地址编码");
        }

        //地址解析
        if(locations.getCode() == 0){
            String addressResolution = MapInfoBasicUtil.addressResolution(locations.getLng(), locations.getLat());
            user.setUserLng(locations.getLng());
            user.setUserLat(locations.getLat());
            user.setUserAddr(addressResolution);

            Users update = usersService.update(user);
            System.out.println("updateUserAddr--addressResolution--user:"+update);

            return Result.buildSuccess();
        }
        //地址编码
        else if(locations.getCode() == 1){
            Locations addressCoding = MapInfoBasicUtil.addressCoding(locations.getAddr());
            user.setUserLng(addressCoding.getLng());
            user.setUserLat(addressCoding.getLat());
            user.setUserAddr(locations.getAddr());

            Users update = usersService.update(user);
            System.out.println("updateUserAddr--addressCoding--user:"+update);

            return Result.buildSuccess();
        }
        //其他异常处理
        else return Result.buildFail("未知错误！");
    }


    /**
     * 修改用户信息
     * 请求时机：修改表单点击“确定”时发起请求
     * @param user 请求修改的用户实体
     * @return 修改成功的用户实体
     */
    @PostMapping("/updateUserInfo")
    public Result<Users> updateUserInfo(@RequestBody Users user){
        Users res = usersService.update(user);
        return Result.buildSuccess(res);
    }


    /**
     * 取消修改用户信息
     * 请求时机：修改表单点击“取消”时发起请求
     * 逻辑：取消修改时，需要将已经修改的信息：头像/定位等，重置回初始状态
     * 但是这两个信息的修改是直接修改了数据库的
     * 而需要通过DetailUser进行重置时不需要完整的用户信息
     * 无参传入
     * @return 取消修改成功的消息
     */
    @GetMapping("/cancelUpdateUserInfo")
    public Result cancelUpdateUserInfo(){
        System.out.println("cancelOldUserInfo:"+oldUser);

        //重置user信息
        Users user = usersService.update(oldUser.getUsers());

        //重置头像信息
        this.updateUserImg(oldUser.getPictures().getPicId(), oldUser.getUsers().getUserId());

        return Result.buildSuccess();
    }


    /**
     * 成为会员--用户主动控制但非自主修改（即用户不是通过表单修改该信息的）
     * 请求时机：用户选择成为会员发起请求
     * 存储用户原始信息时（如有）该请求已经完成
     * @param user 用户实体
     * @return 修改成功的用户实体
     */
    @PostMapping("/becomeAMember")
    public Result becomeAMember(@RequestBody Users user){
        //修改用户角色
        user.setRoleId(3L);
        user.setDiscountTimes(10);
        //由于SHA()没有逆解析，所以这里传递的时SHA()之后的密码，再SHA()就会导致密码改变
        user.setPassword("123456");

        Users res = usersService.update(user);
        return Result.buildSuccess(res);
    }


    /**
     * 身份变更--实时监控用户身份的变化--弃用，改在用户  完成订单-业务层  实现
     * 请求时机：每次订单**完成后**进行判定
     */
    public Result userRoleChange(@RequestBody Users user){
        //折扣次数耗尽，用户失去会员身份
        if(user.getDiscountTimes() == 0){
            user.setRoleId(2L);
            Users update = usersService.update(user);
            return Result.buildSuccess(update);
        }
        //否则返回原对象--方便前端进行统一地数据处理
        return Result.buildSuccess(user);
    }


    /**
     * 获取用户附近景点/酒店信息
     * 请求时机：当用户点击“附近景点”/“附近酒店按钮时”
     * @param pageDto 仅使用地址信息+分页需要的两个参数，code-0-景区，code-1-酒店
     * @return 包含了对应图片的景点/酒店列表
     */
    @PostMapping("/userNearby")
    public Result userNearby(@RequestBody PageDto pageDto) throws Exception {
        //非空判断
        if(pageDto.getLocations().getCode() == null){
            return Result.buildFail("请传入标识符！");
        }

        //获取用户城市信息
        String userCity = NavigationUtil.getUserCity(pageDto.getLocations());
        //非空判断
        if(userCity.equals("")){
            return Result.buildFail("用户定位获取错误！请重新定位！");
        }

        //景区 0
        if(pageDto.getLocations().getCode() == 0){
            //设置城市参数，进行请求
            Landmarks params = new Landmarks();
            params.setCity(userCity);
            pageDto.setLandmarks(params);
            //发起查询请求
            List landmarks = landmarksService.queryAllLmsByPage(pageDto).getList();
            //返回结果集
            ArrayList res = navigationsService.getListsAndPics(landmarks);
            return Result.buildSuccess(res);
        }
        //酒店 1
        else{
            Hotels params = new Hotels();
            params.setCity(userCity);
            pageDto.setHotels(params);

            List hotels = hotelsService.queryAllHotelsByPage(pageDto).getList();

            ArrayList res = navigationsService.getListsAndPics(hotels);
            return Result.buildSuccess(res);
        }

    }

    //用户管理
    //查
    @PostMapping("/queryByPage")
    public Result queryByPage(@RequestBody PageDto pageDto){
        PageInfo list = usersService.queryAllUsersByPage(pageDto);
        if(list.getList().isEmpty())return Result.buildFail("无用户数据");
        ArrayList res = navigationsService.getListsAndPics(list.getList());
        return Result.buildSuccess(res);
    }
    //删
    @GetMapping("/deleteById")
    public Result deleteById(Long userId){
        boolean delete = usersService.deleteById(userId);
        if(delete)return Result.buildSuccess();
        return Result.buildFail("删除失败！");
    }



}
